home *** CD-ROM | disk | FTP | other *** search
/ Gekkan Dennou Club 145 / Gekkan Dennou Club - 2000.6 Vol. 145 (Japan).7z / Gekkan Dennou Club - 2000.6 Vol. 145 (Japan) (Track 1).bin / games / spassion / source.lzh / SOURCE / ESHOT.C < prev    next >
Text File  |  2000-03-31  |  24KB  |  916 lines

  1. /*
  2. #include <stdio.H>
  3. #include <iocslib.H>
  4. */
  5. #include <XSP2lib.H>
  6. #include "SPASSION.H"
  7. #include "PLAYER.H"
  8. #include "ENEMY.H"
  9. #include "ESHOT.H"
  10. #include "PRIORITY.H"
  11. #include "BG.H"
  12. #include "SOUND.H"
  13. #include "SUB.H"
  14. #ifndef NULL
  15. #define NULL ((void *) 0)
  16. #endif
  17.  
  18. #define X_MIN (16)
  19. #define X_MAX (16+256)
  20. #define Y_MIN (16)
  21. #define Y_MAX (16+256)
  22. #define    SWAP(x,y)    ((x)^=(y)^=(x)^=(y))
  23.  
  24. #define ESHOT_MAX 200
  25. static ESHOT eshot[ ESHOT_MAX ];
  26.  
  27. static ESHOT *eshot_free = 0,
  28.  *eshot_top = 0;
  29.  
  30. static void InitEShotEng01( ESHOT * );
  31. static void InitEShotEng02( ESHOT * );
  32. static void InitEShotEng03( ESHOT * );
  33. static void InitEShotNomal( ESHOT * );
  34. static void InitEShotSyuriken( ESHOT * );
  35. static void InitEShotEnergy01( ESHOT * );
  36. static void InitEShotEnergy02( ESHOT * );
  37. static void InitEShotEnergy03( ESHOT * );
  38. static void InitEShotRing01( ESHOT * );
  39. static void InitEShotRing02( ESHOT * );
  40. static void InitEShotLaser00( ESHOT * );
  41. static void InitEShotCutter( ESHOT * );
  42. static void InitEShotHoming( ESHOT * );
  43. static void InitEShotParachute( ESHOT * );
  44. static void InitEShotParabola( ESHOT * );
  45. static void InitEShotLaser01( ESHOT * );
  46. static void InitEShotLaserEX( ESHOT * );
  47.  
  48. static short MoveShot1( ESHOT * );
  49. static short MoveShot2( ESHOT * );
  50. static short MoveShot3( ESHOT * );
  51. static short MoveShot4( ESHOT * );
  52. static short MoveShot5( ESHOT * );
  53. static short MoveShot6( ESHOT * );
  54. static short MoveShot7( ESHOT * );
  55.  
  56. static short eng1_pt[]={0x34,-1};
  57. static short eng2_pt[]={0x35,-1};
  58. static short eng3_pt[]={0x36,-1};
  59. static short nomal_pt[] ={0x37,-1};
  60. static short syuriken_pt[]={0x20,0x21,0x22,0x23,0x24,0x25,0x26,0x27,-1};
  61. static short energy1_pt[]={0x28,0x29,0x2A,0x2B,-1};
  62. static short energy2_pt[]={0x2C,0x2D,0x2E,0x2F,-1};
  63. static short ring1_pt[]={0x10,0x11,0x12,0x13,0x14,0x15,0x16,0x17,-1};
  64. static short ring2_pt[]={0x18,0x19,0x1A,0x1B,0x1C,0x1D,0x1E,0x1F,-1};
  65. static short homing_pt[] ={0x47,-1};
  66. static short laser00_pt[] ={0x59,-1};
  67. static short cutter_pt[] ={0x62,-1};
  68. static short energy3_pt[] ={0x6B,0x6C,0x6D,0x6E,-1};
  69. static short parachute_pt[]={0x70,-1};
  70. static short parabola_pt[]={0x6F,-1};
  71.  
  72. static HIT_XY eng1_p_hit[2]={2,2,-1,-1},eng1_o_hit[2];
  73. static HIT_XY eng2_p_hit[2]={4,4,-1,-1},eng2_o_hit[2];
  74. static HIT_XY eng3_p_hit[2]={8,8,-1,-1},eng3_o_hit[2];
  75. static HIT_XY nomal_p_hit[10]={1,4, 1,3, 1,3, 1,3, 2,2, 2,2, 3,1, 3,1, 4,1,-1,-1},nomal_o_hit[10];
  76. static HIT_XY syuriken_p_hit[2]={4,4,-1,-1},syuriken_o_hit[2];
  77. static HIT_XY energy1_p_hit[2]={4,4,-1,-1},energy1_o_hit[2];
  78. static HIT_XY energy2_p_hit[5]={4,4,3,5,4,4,5,3,-1,-1},energy2_o_hit[5];
  79. static HIT_XY ring1_p_hit[2]={5,5,-1,-1},ring1_o_hit[2];
  80. static HIT_XY ring2_p_hit[2]={7,7,-1,-1},ring2_o_hit[2];
  81. static HIT_XY homing_p_hit[10]={1,4, 1,3, 1,3, 1,3, 2,2, 2,2, 3,1, 3,1, 4,1 ,-1,-1},homing_o_hit[10];
  82. static HIT_XY laser00_p_hit[10]={2,8,3,7,3,6,4,6,5,5,6,4,6,4,7,3,8,2,-1,-1},laser00_o_hit[10];
  83. static HIT_XY cutter_p_hit[10]={4,6,4,4,4,4,4,4,4,4,4,4,4,4,4,4,7,4,-1,-1},cutter_o_hit[10];
  84. static HIT_XY energy3_p_hit[5]={4,7,5,5,7,4,5,5,-1,-1},energy3_o_hit[5];
  85. static HIT_XY parachute_p_hit[2]={2,2,-1,-1},parachute_o_hit[2];
  86. static HIT_XY parabola_p_hit[2]={8,8,-1,-1},parabola_o_hit[2];
  87. static HIT_XY laser01_p_hit[1],laser01_o_hit[1];
  88. static HIT_XY laserex_p_hit[1],laserex_o_hit[1];
  89.  
  90. short    *pt[]={
  91.     eng1_pt,
  92.     eng2_pt,
  93.     eng3_pt,
  94.     nomal_pt,
  95.     syuriken_pt,
  96.     energy1_pt,
  97.     energy2_pt,
  98.     energy3_pt,
  99.     ring1_pt,
  100.     ring2_pt,
  101.     laser00_pt,
  102.     cutter_pt,
  103.     homing_pt,
  104.     parachute_pt,
  105.     parabola_pt,
  106.     NULL
  107. };
  108. HIT_XY    *hit_p[]={
  109.     eng1_p_hit,
  110.     eng2_p_hit,
  111.     eng3_p_hit,
  112.     nomal_p_hit,
  113.     syuriken_p_hit,
  114.     energy1_p_hit,
  115.     energy2_p_hit,
  116.     energy3_p_hit,
  117.     ring1_p_hit,
  118.     ring2_p_hit,
  119.     laser00_p_hit,
  120.     cutter_p_hit,
  121.     homing_p_hit,
  122.     parachute_p_hit,
  123.     parabola_p_hit
  124. };
  125. HIT_XY    *hit_o[]={
  126.     eng1_o_hit,
  127.     eng2_o_hit,
  128.     eng3_o_hit,
  129.     nomal_o_hit,
  130.     syuriken_o_hit,
  131.     energy1_o_hit,
  132.     energy2_o_hit,
  133.     energy3_o_hit,
  134.     ring1_o_hit,
  135.     ring2_o_hit,
  136.     laser00_o_hit,
  137.     cutter_o_hit,
  138.     homing_o_hit,
  139.     parachute_o_hit,
  140.     parabola_o_hit
  141. };
  142.  
  143.  
  144. typedef void (*func_init) (struct ESHOT *);
  145. func_init FuncEShotInit[]=
  146. {
  147.     InitEShotEng01,
  148.     InitEShotEng02,
  149.     InitEShotEng03,
  150.     InitEShotNomal,
  151.     InitEShotSyuriken,
  152.     InitEShotEnergy01,
  153.     InitEShotEnergy02,
  154.     InitEShotEnergy03,
  155.     InitEShotRing01,
  156.     InitEShotRing02,
  157.     InitEShotLaser00,
  158.     InitEShotCutter,
  159.     InitEShotHoming,
  160.     InitEShotParachute,
  161.     InitEShotParabola,
  162.     InitEShotLaser01,
  163.     InitEShotLaserEX,
  164. };
  165.  
  166. /* ゲーム開始時に呼ばれる */
  167. void InitEShot0( void )
  168. {
  169.     short    i,j;
  170.  
  171.     for( i=0;pt[i]!=NULL;i++ ){
  172.         for( j=0;pt[i][j]!=-1;j++ ){
  173.                 pt[i][j]+=obj_shot;
  174.         }
  175.         for( j=0;hit_p[i][j].x!=-1;j++ ){
  176.             hit_o[i][j].x=hit_p[i][j].x+OPTION_HIT_X;
  177.             hit_o[i][j].y=hit_p[i][j].y+OPTION_HIT_Y;
  178. /*            hit_p[i][j].x+=PLAYER_HIT_X;
  179.             hit_p[i][j].y+=PLAYER_HIT_Y;
  180. */
  181.         }
  182.     }
  183. }
  184.  
  185. void InitEShot( void )
  186. {
  187.     short i;
  188.  
  189.     eshot_top = NULL;
  190.     eshot_free = eshot;
  191.     for( i = 0 ; i < ESHOT_MAX; i++ )
  192.         eshot[i].next = &eshot[i + 1];
  193.     eshot[ ESHOT_MAX - 1 ].next = NULL;
  194.  
  195.     eshot_erase = 0;
  196. }
  197.  
  198.  
  199. /*
  200.  *        敵弾発生
  201.  */
  202. ESHOT *MakeEShot(short type, signed short x, signed short y,
  203.                unsigned char speed, unsigned char angle, signed short t, 
  204.                short arg, ENEMY *enemy)
  205. {
  206.     ESHOT *eshot;
  207.  
  208.     /* 空いているか調べる */
  209.     if ( !eshot_free ) return NULL;
  210.  
  211.     /* 空いているのを探す */
  212.     eshot = eshot_free;
  213.     eshot_free = eshot->next;
  214.  
  215.     /* 使っているリストに入れる */
  216.     eshot->next = eshot_top;
  217.     eshot_top = eshot;
  218.  
  219.     /* 各種設定 */
  220.     eshot->lx                = x<<16;
  221.     eshot->ly                = y<<16;
  222.     eshot->vx                = vx_tbl[speed][angle];
  223.     eshot->vy                = vy_tbl[speed][angle];
  224.     eshot->pt                = nomal_pt[0]+pt_rot[angle];
  225.     eshot->type                = type;
  226.     eshot->arg                = arg;
  227.     eshot->state            = 0;
  228.     eshot->angle            = angle;
  229.     eshot->speed            = speed;
  230.     eshot->flg                = 0;
  231.     eshot->anim_count        = 0;
  232.     eshot->count            = 0;
  233.     eshot->enemy            = enemy;
  234.     FuncEShotInit[type](eshot);    /* 初期化ルーチンへ飛ぶ(関数へのポインタってヤツ) */
  235.     return eshot;
  236. }
  237.  
  238. /*
  239.  *        敵弾の移動
  240.  */
  241. void MoveEShot( void )
  242. {
  243.     PLAYER    *pl;
  244.     ESHOT *eshot,*q;
  245.     signed short pl_x, pl_y;
  246.     signed short eshot_x, eshot_y;
  247.  
  248.     eshot = eshot_top;        /* 現在注目しているワーク */
  249.     q     = NULL;            /* 1つ前のワーク(ワーク削除時に必要) */
  250.  
  251.     /* 弾消し中か?(高速化のためやや冗長なコードになってます) */
  252.     if( !eshot_erase ){
  253.         /* 通常の処理(弾消しではない) */
  254.         while( eshot ){
  255.             short    erase_flag=0;
  256. #if 0
  257.             if ( !eshot->func_eshot_move ){        /* 敵弾の移動ルーチンがない? */
  258.                 void game_end();
  259.                 game_end();
  260.             }
  261. #endif
  262.             if ( !( *( eshot->func_eshot_move ) )( eshot ) ) {        /* 弾を移動させる */
  263.                 erase_flag=1;
  264.             } else {                                        /* 消滅していない時 */
  265.                 /* 敵弾と自機の当たり判定 */
  266.                 signed short t, hx = eshot->hit_o->x,hy = eshot->hit_o->y,i,j;
  267.  
  268.                 eshot_x = ESHOT_X;
  269.                 eshot_y = ESHOT_Y;
  270.                 for( i=0,pl=&player[0];i<=play_mode;i++,pl++ ){
  271.                     /* オプションとの当たり判定 */
  272.                     for( j=0;j<2;j++ ){
  273.                         signed short shot_w;
  274.                         if( (t = ESHOT_X + hx) >= (shot_w = *((short *) (&pl->option[j].lx))) ){
  275.                             if( (t -= (short) (hx << 1)) <= shot_w ){
  276.                                 if( (t = ESHOT_Y + hy) >= (shot_w = *((short *) (&pl->option[j].ly))) ){
  277.                                     if( (t -= (short) (hy << 1)) <= shot_w ){
  278. #if 0
  279.                                         printf("OPTION_HIT!!   \n");
  280.                                         printf("j=%d op_x=%d     \n",j,pl->option[j].lx>>16);
  281.                                         printf("esx=%d esy=%d  \n",eshot_x,eshot_y);
  282.                                         printf("esx1=%d esx2=%d  \n",eshot_x - eshot->hit_ox,eshot_x + eshot->hit_ox);
  283.                                         xsp_out();
  284.                                         key_wait();
  285. #endif
  286. /*                                        if( !eshot->laser )*/
  287.                                         if( eshot->type<ESHOT_LASER01 )
  288.                                             erase_flag=1;
  289.                                     }
  290.                                 }
  291.                             }
  292.                         }
  293.                         if( erase_flag )
  294.                             break;
  295.                     }
  296.                     if( erase_flag )
  297.                         break;
  298.  
  299.                     /* プレイヤーとの当たり判定 */
  300.                     pl_x = player->x + 5;pl_y = pl->y;
  301.                     hx=eshot->hit_p->x;
  302.                     hy=eshot->hit_p->y;
  303.                     if( (t = eshot_x - hx) <= pl_x ){
  304.                         if( (t += (short) (hx << 1)) >= pl_x ){
  305.                             if( (t = eshot_y + hy) >= pl_y ){
  306.                                 if( (t -= (short) (hy << 1)) <= pl_y ){
  307. #if 1
  308.                                     if( player->state == PLAYER_ALIVE ){
  309.                                         if( !player->muteki_count )
  310.                                             pl->state = PLAYER_DEAD;        /* プレイヤー撃破 */
  311.                                     }
  312. #endif
  313. #if 0
  314.                                     printf("PLAYER_HIT!!   \n");
  315.                                     printf("i=%d p_x=%d px=%d py=%d    \n",i,player->x,player->x+6,player->y);
  316.                                     printf("es_x=%d es_x1=%d es_x2=%d  \n",eshot_x,eshot_x - hx,eshot_x + hx);
  317.                                     printf("es_y=%d es_y1=%d es_y2=%d  \n",eshot_y,eshot_y - hy,eshot_y + hy);
  318.                                     xsp_out();
  319.                                     key_wait();
  320. #endif
  321.  
  322. /*                                    if( !eshot->laser )*/
  323.                                     if( eshot->type<ESHOT_LASER01 )
  324.                                         erase_flag=1;
  325.                                 }
  326.                             }
  327.                         }
  328.                     }
  329.                     if( erase_flag )
  330.                         break;
  331.                 }
  332.             }
  333.             if( erase_flag ){
  334.                 if (q == NULL) {    /* リストの一番最初を削除 */
  335.                     eshot_top = eshot->next;
  336.                     eshot->next = eshot_free;
  337.                     eshot_free = eshot;
  338.                     q = NULL;
  339.                     eshot = eshot_top;
  340.                 } else {
  341.                     q->next = eshot->next;
  342.                     eshot->next = eshot_free;
  343.                     eshot_free = eshot;
  344.                     eshot = q->next;
  345.                 }
  346.             }else{
  347.                 q     = eshot;
  348.                 eshot = eshot->next;
  349.             }
  350.         }
  351.     }else{
  352.         /* 弾消し中 */
  353.         char erase_flag;/* キャラクターを消す場合 =!0 */
  354.         unsigned short erase_table[14] =
  355.         {0x17, 0x17, 0x17, 0x18, 0x18, 0x18, 0x19, 0x19, 0x19, 0x1A, 0x1A, 0x1A, 0x1B, 0x1B};
  356.         while( eshot ){
  357.             signed short p_x, p_y;
  358.             if (eshot_erase > 1)
  359.                 erase_flag = 0;
  360.             else
  361.                 erase_flag = !0;        /* 最後までアニメーションしたら消す */
  362. #ifdef DEBUG
  363.             eshot_sum++;
  364. #endif
  365.  
  366.             /* 速度を足して上位ワード(固定整数部)だけ取り出す */
  367.             p_x = eshot->x = ((eshot->lx += eshot->vx) >> 16)-8;    /*-8は表示位置をずらすため*/
  368.             p_y = eshot->y = ((eshot->ly += eshot->vy) >> 16)-8;
  369.  
  370.             /* 敵弾が画面外に出たか? */
  371.             /* (画面右から出た判定と左から出た判定を1回の比較で行っている) */
  372.             /* (unsigned short)に型変換することで256+16オーバーにしてるんですね、すごいっす */
  373.             if (((unsigned short) p_x > 256 + 16) || ((unsigned short) p_y > 256 + 16)) {
  374. /*                if( eshot->type<ESHOT_LASER01 )*/
  375.                     erase_flag = !0;
  376.             } else {
  377.                 if( eshot->type<ESHOT_LASER01 ){
  378.                     eshot->pt = obj_obj + erase_table[eshot_erase];
  379.                     eshot->info = 0x0430;
  380.                     xsp_set_st(eshot);
  381.                 }
  382.             }
  383.  
  384.             if( erase_flag ){
  385. /*                if( eshot->laser ){*/
  386.                 if( eshot->type>=ESHOT_LASER01 ){
  387.                     extern BOX_PTR    *old_box_buf[32];
  388.                     extern short    old_box_num;
  389.                     eshot->box.color=0;
  390.                     old_box_buf[old_box_num++]=&eshot->box;
  391.                     old_box_num&=31;
  392.                     old_box_buf[old_box_num]=(BOX_PTR *)0;
  393.                 }
  394.                 if (q == NULL) {    /* リストの一番最初を削除 */
  395.                     eshot_top = eshot->next;
  396.                     eshot->next = eshot_free;
  397.                     eshot_free = eshot;
  398.                     q = NULL;
  399.                     eshot = eshot_top;
  400.                 } else {
  401.                     q->next = eshot->next;
  402.                     eshot->next = eshot_free;
  403.                     eshot_free = eshot;
  404.                     eshot = q->next;
  405.                 }
  406.             }else{
  407.                 q     = eshot;
  408.                 eshot = eshot->next;
  409.             }
  410.         }
  411.         eshot_erase--;
  412.     }
  413. }
  414.  
  415. /*
  416.  *        敵弾消滅
  417.  */
  418. #if 0
  419. ESHOT *EraseEShot( ESHOT *eshot )
  420. {
  421.     ESHOT *next;
  422.  
  423.     next = eshot->next;
  424.     eshot->type = 0;
  425.  
  426.     /* 使っているリストから抜く */
  427.     if ( eshot->pre ) {
  428.         eshot->pre->next = eshot->next;
  429.         if ( eshot->next ) eshot->next->pre = eshot->pre;
  430.     } else {
  431.         if ( eshot->next ) eshot->next->pre = 0;
  432.         eshot_top = eshot->next;
  433.     }
  434.  
  435.     /* 空いているリストに入れる */
  436.     eshot->pre = 0;
  437.     eshot->next = eshot_free;
  438.     eshot_free = eshot;
  439.  
  440.     return next;
  441. }
  442. #endif
  443.  
  444. static void InitEShotEng01( ESHOT *eshot )
  445. {
  446.     eshot->pt                = eng1_pt[0];
  447.     eshot->info                = 0x0300|PRIORITY_ESHOT;
  448.     eshot->pt_                = &eng1_pt[0];
  449.     eshot->hit_p            = eng1_p_hit;
  450.     eshot->hit_o            = eng1_o_hit;
  451.     eshot->func_eshot_move    = MoveShot2;
  452.     eshot->laser=0;
  453.     return;
  454. }
  455. static void InitEShotEng02( ESHOT *eshot )
  456. {
  457.     eshot->pt                = eng2_pt[0];
  458.     eshot->info                = 0x0300|PRIORITY_ESHOT;
  459.     eshot->pt_                = &eng2_pt[0];
  460.     eshot->hit_p            = eng2_p_hit;
  461.     eshot->hit_o            = eng2_o_hit;
  462.     eshot->func_eshot_move    = MoveShot2;
  463.     eshot->laser=0;
  464.     return;
  465. }
  466.  
  467. static void InitEShotEng03( ESHOT *eshot )
  468. {
  469.     eshot->pt                = eng3_pt[0];
  470.     eshot->info                = 0x0300|PRIORITY_ESHOT;
  471.     eshot->pt_                = &eng3_pt[0];
  472.     eshot->hit_p            = eng3_p_hit;
  473.     eshot->hit_o            = eng3_o_hit;
  474.     eshot->func_eshot_move    = MoveShot2;
  475.     eshot->laser=0;
  476.     return;
  477. }
  478. static void InitEShotNomal( ESHOT *eshot )
  479. {
  480.     eshot->pt                = nomal_pt[0]+pt_rot[eshot->angle];
  481.     eshot->info                = 0x0300|PRIORITY_ESHOT|info_rot[eshot->angle];
  482.     eshot->pt_                = &nomal_pt[0];
  483.     eshot->hit_p            = nomal_p_hit;
  484.     eshot->hit_o            = nomal_o_hit;
  485.     eshot->func_eshot_move    = MoveShot2;
  486.     eshot->laser=0;
  487.     return;
  488. }
  489. static void InitEShotSyuriken( ESHOT *eshot )
  490. {
  491.     eshot->pt                = syuriken_pt[0];
  492.     eshot->info                = 0x0300|PRIORITY_ESHOT;
  493.     eshot->pt_                = &syuriken_pt[0];
  494.     eshot->hit_p            = syuriken_p_hit;
  495.     eshot->hit_o            = syuriken_o_hit;
  496.     eshot->func_eshot_move    = MoveShot1;
  497.     eshot->laser=0;
  498.     return;
  499. }
  500. static void InitEShotEnergy01( ESHOT *eshot )
  501. {
  502.     eshot->pt                = energy1_pt[0];
  503.     eshot->info                = 0x0300|PRIORITY_ESHOT;
  504.     eshot->pt_                = &energy1_pt[0];
  505.     eshot->hit_p            = energy1_p_hit;
  506.     eshot->hit_o            = energy1_o_hit;
  507.     eshot->func_eshot_move    = MoveShot1;
  508.     eshot->laser=0;
  509.     return;
  510. }
  511. static void InitEShotEnergy02( ESHOT *eshot )
  512. {
  513.     eshot->pt                = energy2_pt[0];
  514.     eshot->info                = 0x0300|PRIORITY_ESHOT;
  515.     eshot->pt_                = &energy2_pt[0];
  516.     eshot->hit_p            = energy2_p_hit;
  517.     eshot->hit_o            = energy2_o_hit;
  518.     eshot->func_eshot_move    = MoveShot1;
  519.     eshot->laser=0;
  520.     return;
  521. }
  522. static void InitEShotEnergy03( ESHOT *eshot )
  523. {
  524.     eshot->pt                = energy3_pt[0];
  525.     eshot->info                = 0x0300|PRIORITY_ESHOT;
  526.     eshot->pt_                = &energy3_pt[0];
  527.     eshot->hit_p            = energy3_p_hit;
  528.     eshot->hit_o            = energy3_o_hit;
  529.     eshot->func_eshot_move    = MoveShot1;
  530.     eshot->laser=0;
  531.     return;
  532. }
  533. static void InitEShotRing01( ESHOT *eshot )
  534. {
  535.     eshot->pt                = ring1_pt[0];
  536.     eshot->info                = 0x0300|PRIORITY_ESHOT;
  537.     eshot->pt_                = &ring1_pt[0];
  538.     eshot->hit_p            = ring1_p_hit;
  539.     eshot->hit_o            = ring1_o_hit;
  540.     eshot->func_eshot_move    = MoveShot1;
  541.     eshot->laser=0;
  542.     return;
  543. }
  544. static void InitEShotRing02( ESHOT *eshot )
  545. {
  546.     eshot->pt                = ring2_pt[0];
  547.     eshot->info                = 0x0300|PRIORITY_ESHOT;
  548.     eshot->pt_                = &ring2_pt[0];
  549.     eshot->hit_p            = ring2_p_hit;
  550.     eshot->hit_o            = ring2_o_hit;
  551.     eshot->func_eshot_move    = MoveShot1;
  552.     eshot->laser=0;
  553.     return;
  554. }
  555. static void InitEShotLaser00( ESHOT *eshot )
  556. {
  557.     eshot->pt                = laser00_pt[0]+pt_rot[eshot->angle];
  558.     eshot->info                = 0x0300|PRIORITY_ESHOT|info_rot[eshot->angle];
  559.     eshot->pt_                = &laser00_pt[0];
  560.     eshot->hit_p            = laser00_p_hit;
  561.     eshot->hit_o            = laser00_o_hit;
  562.     eshot->func_eshot_move    = MoveShot2;
  563.     eshot->laser=0;
  564.     return;
  565. }
  566. static void InitEShotCutter( ESHOT *eshot )
  567. {
  568.     eshot->pt                = cutter_pt[0]+pt_rot[eshot->angle];
  569.     eshot->info                = 0x0300|PRIORITY_ESHOT|info_rot[eshot->angle];
  570.     eshot->pt_                = &cutter_pt[0];
  571.     eshot->hit_p            = cutter_p_hit;
  572.     eshot->hit_o            = cutter_o_hit;
  573.     eshot->func_eshot_move    = MoveShot2;
  574.     eshot->laser=0;
  575.     return;
  576. }
  577. static void InitEShotHoming( ESHOT *eshot )
  578. {
  579.     eshot->pt                = homing_pt[0]+pt_rot[eshot->angle];
  580.     eshot->info                = 0x0300|PRIORITY_ESHOT|info_rot[eshot->angle];
  581.     eshot->pt_                = &homing_pt[0];
  582.     eshot->hit_p            = homing_p_hit;
  583.     eshot->hit_o            = homing_o_hit;
  584.     eshot->func_eshot_move    = MoveShot3;
  585.     eshot->laser=0;
  586.     return;
  587. }
  588. static void InitEShotParachute( ESHOT *eshot )
  589. {
  590.     static unsigned char seed=0;
  591.  
  592.     eshot->pt                = parachute_pt[0]+pt_rot[eshot->angle];
  593.     eshot->info                = 0x0900|PRIORITY_ESHOT;
  594.     eshot->pt_                = ¶chute_pt[0];
  595.     eshot->hit_p            = parachute_p_hit;
  596.     eshot->hit_o            = parachute_o_hit;
  597.     eshot->func_eshot_move    = MoveShot4;
  598.     eshot->laser=0;
  599.     eshot->angle=128;
  600.     if( rndtable[seed++]>128 )
  601.         eshot->state=0;
  602.     else
  603.         eshot->state=1;
  604.     seed&=255;
  605.     return;
  606. }
  607. static void InitEShotParabola( ESHOT *eshot )
  608. {
  609.     eshot->pt                = parabola_pt[0];
  610.     eshot->info                = 0x0300|PRIORITY_ESHOT;
  611.     eshot->pt_                = ¶bola_pt[0];
  612.     eshot->hit_p            = parabola_p_hit;
  613.     eshot->hit_o            = parabola_o_hit;
  614.     eshot->func_eshot_move    = MoveShot5;
  615.     eshot->laser=0;
  616.     return;
  617. }
  618. static void InitEShotLaser01( ESHOT *eshot )
  619. {
  620.     eshot->laser=1;
  621.     eshot->box.x1=eshot->box.x2=eshot->old_box.x1=eshot->old_box.x2 = eshot->enemy->x;
  622.     eshot->box.y1=eshot->box.y2=eshot->old_box.y1=eshot->old_box.y2 = eshot->enemy->y;
  623.     eshot->box.color        = 0xFF;
  624.     eshot->old_box.color    = 0;
  625.     eshot->hit_p            = laser01_p_hit;
  626.     eshot->hit_o            = laser01_o_hit;
  627.     eshot->func_eshot_move    = MoveShot6;
  628.     return;
  629. }
  630. static void InitEShotLaserEX( ESHOT *eshot )
  631. {
  632.     eshot->laser=1;
  633.     eshot->box.x1=eshot->box.x2=eshot->old_box.x1=eshot->old_box.x2 = eshot->enemy->x;
  634.     eshot->box.y1=eshot->box.y2=eshot->old_box.y1=eshot->old_box.y2 = eshot->enemy->y;
  635.     eshot->box.color        = 0xFF;
  636.     eshot->old_box.color    = 0;
  637.     eshot->hit_p            = laserex_p_hit;
  638.     eshot->hit_o            = laserex_o_hit;
  639.     eshot->func_eshot_move    = MoveShot7;
  640.     return;
  641. }
  642.  
  643.  
  644. /* アニメーションする */
  645. static short    MoveShot1( ESHOT *es )
  646. {
  647.     short    es_x,es_y,pt;
  648.  
  649.     /* 速度を足して上位ワード(固定整数部)だけ取り出す */
  650.     es_x = ((es->lx += es->vx) >> 16);
  651.     es_y = ((es->ly += es->vy) >> 16);
  652.     es->x = es_x-8;        /*-8は表示位置をずらすため*/
  653.     es->y = es_y-8;
  654.  
  655.     if(((unsigned short) es_x > 256 + 16) || ((unsigned short) es_y > 256 + 16)
  656.      || (CheckBGHit(es_x-16,es_y-16)!=NON_BG) )
  657.         return 0;
  658.  
  659.     pt=es->pt_[(es->anim_count++)/4];
  660.     if( pt == -1 ){
  661.         pt=es->pt_[0];
  662.         es->anim_count=0;
  663.     }
  664.     es->pt = pt;
  665.  
  666.     xsp_set_st( es );
  667.     return 1;
  668. }
  669.  
  670. /* アニメーションしない */
  671. static short    MoveShot2( ESHOT *eshot )
  672. {
  673.     short    es_x,es_y;
  674.  
  675.     /* 速度を足して上位ワード(固定整数部)だけ取り出す */
  676.     es_x = ((eshot->lx += eshot->vx) >> 16);
  677.     es_y = ((eshot->ly += eshot->vy) >> 16);
  678.     eshot->x = es_x-8;        /*-8は表示位置をずらすため*/
  679.     eshot->y = es_y-8;
  680.  
  681.     if(((unsigned short) es_x > 256 + 16) || ((unsigned short) es_y > 256 + 16)
  682.      || (CheckBGHit(es_x-16,es_y-16)!=NON_BG) )
  683.         return 0;
  684.  
  685.     xsp_set_st( eshot );
  686.     return 1;
  687. }
  688. #if 0
  689. static short    MoveShot2_B( ESHOT *eshot )
  690. {
  691.     /* 速度を足して上位ワード(固定整数部)だけ取り出す */
  692.     eshot->x = ((eshot->lx += eshot->vx) >> 16);
  693.     eshot->y = ((eshot->ly += eshot->vy) >> 16);
  694.  
  695.     if(((unsigned short) eshot->x > 256 + 16) || ((unsigned short) eshot->y > 256 + 16)
  696.      || (CheckBGHit(eshot->x-16,eshot->y-16)!=NON_BG) )
  697.         return 0;
  698.  
  699.     xobj_set_st( eshot );
  700.     return 1;
  701. }
  702. #endif
  703.  
  704.  
  705. /* ホーミング */
  706. short    MoveShot3( ESHOT *es )
  707. {
  708.     short    es_x,es_y,tmp,anim_num,num,pt[2]={0,9};
  709.     short    pl_x=player[0].x,pl_y=player[0].y;
  710.     HIT_XY    *hit_p=homing_p_hit;
  711.     HIT_XY    *hit_o=homing_o_hit;
  712.  
  713.     /* 速度を足して上位ワード(固定整数部)だけ取り出す */
  714.     es_x = ((es->lx += es->vx) >> 16);
  715.     es_y = ((es->ly += es->vy) >> 16);
  716.     es->x = es_x-8;        /*-8は表示位置をずらすため*/
  717.     es->y = es_y-8;
  718.  
  719.     if( (anim_num=((es->anim_count++)/4)) > 1 ){
  720.         es->anim_count=0;
  721.         anim_num=0;
  722.     }
  723.     es->pt     = homing_pt[0]+(num=pt_rot[es->angle])+pt[anim_num];
  724.     es->info = (es->info & 0x0FFF) | info_rot[es->angle];
  725.     es->hit_p=&hit_p[num];es->hit_o=&hit_o[num];
  726.  
  727.     if( es->count++ > 4 && es->state < 32 ) {        /* 4 回移動するごとに向き修正、32 回追いかけたら終わり */
  728.         tmp = calc_direction(es_x, es_y, pl_x, pl_y);
  729.  
  730.         tmp = (tmp - es->angle) & (256 - 1);
  731.         if( tmp ) {
  732.             if (tmp > 127) es->angle-=8 ;
  733.             else es->angle+=8 ;
  734.             es->angle &= 256 - 1;
  735.         }
  736.  
  737.         es->vx = vx_tbl[es->speed][es->angle];
  738.         es->vy = vy_tbl[es->speed][es->angle];
  739.         es->state++;
  740.         es->count=0;
  741.     }else{
  742.         if(((unsigned short) es_x > 256 + 16) || ((unsigned short) es_y > 256 + 16)
  743.          || (CheckBGHit(es_x-16,es_y-16)!=NON_BG) )
  744.             return 0;
  745.     }
  746.  
  747.     xsp_set_st( es );
  748.     return 1;
  749. }
  750.  
  751.  
  752. /* 落下傘 */
  753. short    MoveShot4( ESHOT *es )
  754. {
  755.     short    anim_pt=0;
  756.  
  757.     /* 速度を足して上位ワード(固定整数部)だけ取り出す */
  758.     es->x = ((es->lx += es->vx) >> 16);
  759.     es->y = ((es->ly += es->vy) >> 16);
  760.  
  761.     if( es->vy > 65536/4 ){            /* 下向き */
  762.         if( !es->state ){
  763.             if( ++es->angle>128+32 ){
  764.                 es->angle=128+32;
  765.                 es->state=1;
  766.             }
  767.         }else{
  768.             if( --es->angle<128-32 ){
  769.                 es->angle=128-32;
  770.                 es->state=0;
  771.             }
  772.         }
  773.         if( es->anim_count++ > 4 ){
  774.             anim_pt=9;
  775.             if( es->anim_count > 8 )
  776.                 es->anim_count=0;
  777.         }
  778.         es->pt = obj_shot_b+15 + ((es->angle-96) >> 3)+anim_pt;
  779.         es->vx=vx_tbl[8][es->angle];
  780.         if(((unsigned short) es->x > 256 + 16) || ((unsigned short) es->y > 256 + 16)
  781.          || (CheckBGHit(es->x-16,es->y-16)!=NON_BG) )
  782.             return 0;
  783.         xobj_set_st( es );
  784.     }else{                            /* 上向き */
  785.         es->vy += 4096;
  786.         es->x -= 8;        /*-8は表示位置をずらすため*/
  787.         es->y -= 8;
  788.         if( es->anim_count++ > 4 ){
  789.             anim_pt=1;
  790.             if( es->anim_count > 8 )
  791.                 es->anim_count=0;
  792.         }
  793.         es->pt = obj_shot+0x70+anim_pt;
  794.         xsp_set_st( es );
  795.     }
  796.  
  797.     return 1;
  798. }
  799.  
  800. /* 放物線 */
  801. short    MoveShot5( ESHOT *es )
  802. {
  803.     short    es_x,es_y;
  804.  
  805.     /* 速度を足して上位ワード(固定整数部)だけ取り出す */
  806.     es_x = ((es->lx += es->vx) >> 16);
  807.     es_y = ((es->ly += es->vy) >> 16);
  808.     es->x = es_x-8;        /*-8は表示位置をずらすため*/
  809.     es->y = es_y-8;
  810.  
  811.     if(((unsigned short) es_x > 256 + 16) || ((unsigned short) es_y > 256 + 16)
  812.      || (CheckBGHit(es_x-16,es_y-16)!=NON_BG) )
  813.         return 0;
  814.  
  815.     if( (es->vy += 4096) > 2*65536 )
  816.         es->vy = 2*65536;
  817.  
  818.     xsp_set_st( es );
  819.     return 1;
  820. }
  821.  
  822. /* 横レーザー */
  823. short    MoveShot6( ESHOT *es )
  824. {
  825.     extern BOX_PTR    *old_box_buf[32],*box_buf[32];
  826.     extern short    old_box_num,box_num;
  827.     signed short t;
  828.  
  829.     es->old_box.x1=es->box.x1;
  830.     es->old_box.y1=es->box.y1;
  831.     es->old_box.x2=es->box.x2;
  832.     es->old_box.y2=es->box.y2;
  833.     if( es->box.x1 >= 0 ){                /* レーザーの端が画面外に出るまで伸びる */
  834.         es->box.x2=es->enemy->x+es->box_x;
  835.         es->box.x1-=4;
  836.         if( es->box.x1>es->box.x2 )es->box.x1=es->box.x2-4;
  837.     }else{
  838.         es->box.x1-=4;
  839.         es->box.x2-=4;
  840.     }
  841.     es->x=(es->box.x1+es->box.x2)/2;
  842.     es->hit_p->x=(t=es->x-es->box.x1)+PLAYER_HIT_X;
  843.     es->hit_o->x=t+OPTION_HIT_X;
  844.  
  845.     es->box.y1=es->box.y2=es->y=es->enemy->y+es->box_y;
  846.     es->hit_p->y=1+PLAYER_HIT_Y;
  847.     es->hit_o->y=1+OPTION_HIT_Y;
  848.  
  849.     es->lx=(es->x+16) << 16;
  850.     es->ly=(es->y+16) << 16;
  851.  
  852.     old_box_buf[old_box_num++]=&es->old_box;
  853.     old_box_num&=31;
  854.     old_box_buf[old_box_num]=(BOX_PTR *)0;
  855.  
  856.     if( es->box.x2 < 0 || es->box.x1 > 255 )
  857.         return 0;
  858.  
  859.     box_buf[box_num++]=&es->box;
  860.     box_num&=31;
  861.     box_buf[box_num]=(BOX_PTR *)0;
  862.  
  863.     return 1;
  864. }
  865.  
  866. /* あとから太くなる横レーザー */
  867. short    MoveShot7( ESHOT *es )
  868. {
  869.     extern BOX_PTR    *old_box_buf[32],*box_buf[32];
  870.     extern short    old_box_num,box_num;
  871.     signed short t;
  872.  
  873.     es->old_box.x1=es->box.x1;
  874.     es->old_box.y1=es->box.y1;
  875.     es->old_box.x2=es->box.x2;
  876.     es->old_box.y2=es->box.y2;
  877.     if( es->box.x1 >= 0 ){                /* レーザーの端が画面外に出るまで伸びる */
  878.         es->box.x2=es->enemy->x+es->box_x;
  879.         es->box.x1-=2;
  880.         if( es->box.x1>es->box.x2 )es->box.x1=es->box.x2-4;
  881.         es->box.y1=es->box.y2=es->y=es->enemy->y+es->box_y;
  882.     }else{
  883.         if(es->count++<12){
  884.             es->box.y1=(es->y=es->enemy->y+es->box_y)-es->count/4;
  885.             es->box.y2=(es->y=es->enemy->y+es->box_y)+es->count/4;
  886.         }else{
  887.             es->box.x1-=2;
  888.             es->box.x2-=2;
  889.         }
  890.     }
  891.     es->x=(es->box.x1+es->box.x2)/2;
  892.     es->hit_p->x=(t=es->x-es->box.x1)+PLAYER_HIT_X;
  893.     es->hit_o->x=t+OPTION_HIT_X;
  894.  
  895.     es->hit_p->y=1+PLAYER_HIT_Y;
  896.     es->hit_o->y=1+OPTION_HIT_Y;
  897.  
  898.     es->lx=(es->x+16) << 16;
  899.     es->ly=(es->y+16) << 16;
  900.  
  901.  
  902. /*printf("x1=%d x2=%d x=%d hx=%d  \n",es->box.x1,es->box.x2,es->x,es->hit_px);*/
  903.  
  904.     old_box_buf[old_box_num++]=&es->old_box;
  905.     old_box_num&=31;
  906.     old_box_buf[old_box_num]=(BOX_PTR *)0;
  907.     if( es->box.x2 < 0 || es->box.x1 > 255 ){
  908.         return 0;
  909.     }
  910.     box_buf[box_num++]=&es->box;
  911.     box_num&=31;
  912.     box_buf[box_num]=(BOX_PTR *)0;
  913.  
  914.     return 1;
  915. }
  916.